package com.itheima.tliaswebmanagement.filter;

import com.alibaba.fastjson2.JSONObject;
import com.itheima.tliaswebmanagement.pojo.Result;
import com.itheima.tliaswebmanagement.utils.JwtUtils;
import jakarta.servlet.*;
import jakarta.servlet.annotation.WebFilter;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.extern.slf4j.Slf4j;
import org.springframework.util.StringUtils;

import java.io.IOException;
import java.io.PrintWriter;

/**
 * 校验用户是否已登录
 */
@WebFilter(urlPatterns = "/*")// 过滤器或拦截器使用一个就行了
@Slf4j
public class LoginCheckFilter implements Filter {
    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        servletRequest.setCharacterEncoding("UTF-8");
        // 强制转换
        HttpServletRequest httpServletRequest = (HttpServletRequest) servletRequest;
        HttpServletResponse httpServletResponse = (HttpServletResponse) servletResponse;
        // 获取请求资源路径
        String requestURL = httpServletRequest.getRequestURL().toString();
        log.info("请求的URL: {}", requestURL);

        if (requestURL.contains("login")) {
            log.info("拦截到登录请求,放行...");
            // 放行
            filterChain.doFilter(servletRequest, servletResponse);
            // 放行之后一定要结束过滤!
            return;
        } else if (requestURL.contains("logo.png")) {
            log.info("拦截到访问Logo请求,放行...");
            filterChain.doFilter(servletRequest, servletResponse);
            return;
        } else if (requestURL.equals("http://localhost:8080/")) {
            filterChain.doFilter(servletRequest, servletResponse);
            return;
        }

        //获取请求中的令牌
        String jwt = httpServletRequest.getHeader("token");

        if (!StringUtils.hasLength(jwt)) {
            //如果没有长度，说明用户未曾登录
            log.info("请求头token字段为空，返回用户未登录的信息");
            Result notLogin = Result.error("NOT_LOGIN");
            PrintWriter writer = servletResponse.getWriter();
            writer.write(JSONObject.toJSONString(notLogin));
            writer.close();
            return;
        }

        // 如果jwt有长度，校验令牌
        try {
            JwtUtils.parseJwt(jwt);
        } catch (Exception e) {
            // 如果捕获到异常，意味着令牌无效，直接反馈给前端用户未登录的信息
            log.info("解析令牌失败,返回用户未登录的信息");
            Result notLogin = Result.error("NOT_LOGIN");
            httpServletResponse.getWriter().write(JSONObject.toJSONString(notLogin));
            return;
        }
        log.info("用户已登录，放行...");
        // 执行到此处说明用户已登录，可以放行
        filterChain.doFilter(servletRequest, servletResponse);
    }
}
